the migrate command:

Execute in Terminal

python3 manage.py migrate

Next, to specify that we want to use Token authentication (instead of Basic authentication or Session authentication

etc.), in todobackend/backend/settings.py, we add:

Modify Bold Code

...

REST_FRAMEWORK = {

'DEFAULT_AUTHENTICATION_CLASSES':[

'rest_framework.authentication.TokenAuthentication',

]

}

User Sign Up

Let’s first implement a new user sign up. We first create a path in todobackend/api/urls.py for the signup endpoint:

Modify Bold Code

from django.urls import path

from . import views

urlpatterns = [

path('todos/', views.TodoListCreate.as_view()),

path('todos/<int:pk>', views.TodoRetrieveUpdateDestroy.as_view()),

path('todos/<int:pk>/complete', views.TodoToggleComplete.as_view()),

path('signup/', views.signup),

]

We then implement the signup view in todobackend/api/views.py by adding the following:

Modify Bold Code

...

from todo.models import Todo

from django.db import IntegrityError

from django.contrib.auth.models import User

from rest_framework.parsers import JSONParser

from rest_framework.authtoken.models import Token

from django.http import JsonResponse

from django.views.decorators.csrf import csrf_exempt

...

class TodoToggleComplete(generics.UpdateAPIView):

...

@csrf_exempt

def signup(request):

if request.method == 'POST':

try:

data = JSONParser().parse(request) # data is a dictionary

user = User.objects.create_user(

username=data['username'],

password=data['password'])

user.save()

token = Token.objects.create(user=user)

return JsonResponse({'token':str(token)},status=201)

except IntegrityError:

return JsonResponse(

{'error':'username taken. choose another username'},

status=400)

Code Explanation

Analyze Code

@csrf_exempt

Because the POST request is coming from a different domain (the frontend domain) and will not have the token

required to pass the CSRF checks (cross site request forgery), we use csrf_exempt for this view.

Analyze Code

def signup(request):

if request.method == 'POST':